#pragma once

#include <map>
#include "BulletEntity.h"

#define BULLET_CONTAINER std::map<int, AbstractEntity*>

class GameBullet {
private:
	BULLET_CONTAINER *playerBullets, *armyBullets;
public:
	GameBullet() {
		initBullets();
	}

	void initBullets() {
		playerBullets = new BULLET_CONTAINER();
		armyBullets = new BULLET_CONTAINER();
	}

	BULLET_CONTAINER* getPlayerBullets() {
		return playerBullets;
	}

	BULLET_CONTAINER* getArmyBullets() {
		return armyBullets;
	}

	void draw(long timetick) {
		BULLET_CONTAINER::iterator it;
		for (it = playerBullets->begin(); it != playerBullets->end(); it++) {
			it->second->draw(timetick);
		}
		for (it = armyBullets->begin(); it != armyBullets->end(); it++) {
			it->second->draw(timetick);
		}
	}

	void update(long timetick) {
		BULLET_CONTAINER::iterator it;
		for (it = playerBullets->begin(); it != playerBullets->end();) {
			if (it->second->getAbstractData()->isDead) {
				it = deleteBullet(it->second, BulletPlayer);
			} else {
				it->second->update(timetick);
				it++;
			}
		}
		for (it = armyBullets->begin(); it != armyBullets->end();) {
			if (it->second->getAbstractData()->isDead) {
				it = deleteBullet(it->second, BulletArmy);
			} else {
				it->second->update(timetick);
				it++;
			}
		}
	}

	// Add bullet to GameBullet by GameDeviceSingleton
	void addBullet(BulletArmies type, BulletEntity* bullet) {
		switch(type) {
		case BulletPlayer:
			playerBullets->insert(std::make_pair(bullet->getAbstractData()->getId(), bullet));
			break;
		case BulletArmy:
			armyBullets->insert(std::make_pair(bullet->getAbstractData()->getId(), bullet));
			break;
		}
	}

	// Delete bullet from GameBullet by GameDeviceSingleton
	BULLET_CONTAINER::iterator deleteBullet(AbstractEntity* entity, BulletArmies type) {
		BULLET_CONTAINER* bullet_container = type == BulletArmy ? armyBullets : playerBullets;
		return deleteBullet(entity, bullet_container);
	}

	BULLET_CONTAINER::iterator deleteBullet(AbstractEntity* bullet, BULLET_CONTAINER* container) {
		BULLET_CONTAINER::iterator it = container->find(bullet->getAbstractData()->getId());
		if (it != container->end()) {
			return container->erase(it);
		}
		return container->end();
	}
};